<?php
/**
 * Created by PhpStorm.
 * User: Administrator
 * Date: 2018/1/7
 * Time: 20:08
 */

namespace Xcx\Controller;

use Xcx\Common\ErrorCode;
use Xcx\Model\SharePhotoModel;

vendor('Xcx.wxBizDataCrypt');

class ShareController extends BaseController
{
    //默认配置
    protected $config = [
        'url' => "https://api.weixin.qq.com/sns/jscode2session", //微信获取session_key接口url
        'appid' => 'wx831f6c86e9bebbce', // APPId
        'secret' => '412f1bd4e378e316beb1692db8c6aa5a', // 秘钥
        'grant_type' => 'authorization_code', // grant_type，一般情况下固定的
    ];

    /**
     * 照片墙分享到群
     */
    public function doPhotoShare()
    {
        $encryptedData = I('encryptedData');
        $iv = I('iv');
        $pid = I('pid');

        $data = $this->getShareData($encryptedData, $iv);
        $arr['code'] = ErrorCode::$Fail;
        if ($data['openGId']) {
            $SharePhoto = new SharePhotoModel();
            $code = $SharePhoto->doSharePhoto($pid,$data['openGId']);
            $arr['code'] = $code;
        }
        $this->ajaxReturn($arr);
    }

    /**
     * 更新用户的sessionKey
     */
    public function updateSessionKey() {
        $code = I('code');

        $sessionData = $this->getSessionKey($code);
        if ($sessionData['code'] == 0) {
            $maps['uid'] = $this->uid;
            $maps['session3rd'] = $this->session3rd;

            $data['session_key'] = $sessionData['session_key'];
            $res = M('login_session')->where($maps)->data($data)->save();
            if ($res) $arr = array('code'=>0);
            else $arr = array('code'=>0);
        } else {
            $arr = array('code'=>$sessionData['code']);
        }

        $this->ajaxReturn($arr);
    }

    /**
     * 获取SessionKey
     * @param $code
     * @return array|mixed
     */
    public function getSessionKey($code)
    {
        $params = [
            'appid' => $this->config['appid'],
            'secret' => $this->config['secret'],
            'js_code' => $code,
            'grant_type' => $this->config['grant_type']
        ];

        $res = $this->makeRequest($this->config['url'], $params);

        if ($res['code'] !== 200 || !isset($res['result']) || !isset($res['result'])) {
            return ['code'=>\ErrorCode::$RequestTokenFailed, 'message'=>'请求Token失败'];
        }
        $reqData = json_decode($res['result'], true);
        if (!isset($reqData['session_key'])) {
            return ['code'=>\ErrorCode::$RequestTokenFailed, 'message'=>'请求Token失败'];
        }

        return ['code'=>0,'session_key'=>$reqData['session_key']];
    }

    /**
     * 获取分享信息
     * @param $encryptedData
     * @param $iv
     * @return array|mixed
     */
    public function getShareData($encryptedData, $iv) {
        /**
         *
         * 6.使用第4步返回的session_key解密encryptData, 将解得的信息与rawData中信息进行比较, 需要完全匹配,
         * 解得的信息中也包括openid, 也需要与第4步返回的openid匹配. 解密失败或不匹配应该返回客户相应错误.
         * （使用官方提供的方法即可）
         */
        $sessionKey = $this->getUserSessionKey();
        $pc = new \WXBizDataCrypt($this->config['appid'], $sessionKey);
        $errCode = $pc->decryptData($encryptedData, $iv, $data );
        if ($errCode !== 0) {
            return ['code'=>\ErrorCode::$EncryptDataNotMatch, 'message'=>'解密信息错误'];
        }

        $data = json_decode($data, true);
        return $data;
    }

    /**
     * 获取用户的sessionKey
     * @return mixed
     */
    public function getUserSessionKey()
    {
        $maps['uid'] = $this->uid;
        $maps['session3rd'] = $this->session3rd;

        $sessionKey =  M('login_session')->where($maps)->getField('session_key');
        return $sessionKey;
    }

    /**
     * 发起http请求
     * @param string $url 访问路径
     * @param array $params 参数，该数组多于1个，表示为POST
     * @param int $expire 请求超时时间
     * @param array $extend 请求伪造包头参数
     * @param string $hostIp HOST的地址
     * @return array    返回的为一个请求状态，一个内容
     */
    public function makeRequest($url, $params = array(), $expire = 0, $extend = array(), $hostIp = '')
    {
        if (empty($url)) {
            return array('code' => '100');
        }

        $_curl = curl_init();
        $_header = array(
            'Accept-Language: zh-CN',
            'Connection: Keep-Alive',
            'Cache-Control: no-cache'
        );
        // 方便直接访问要设置host的地址
        if (!empty($hostIp)) {
            $urlInfo = parse_url($url);
            if (empty($urlInfo['host'])) {
                $urlInfo['host'] = substr(DOMAIN, 7, -1);
                $url = "http://{$hostIp}{$url}";
            } else {
                $url = str_replace($urlInfo['host'], $hostIp, $url);
            }
            $_header[] = "Host: {$urlInfo['host']}";
        }

        // 只要第二个参数传了值之后，就是POST的
        if (!empty($params)) {
            curl_setopt($_curl, CURLOPT_POSTFIELDS, http_build_query($params));
            curl_setopt($_curl, CURLOPT_POST, true);
        }

        if (substr($url, 0, 8) == 'https://') {
            curl_setopt($_curl, CURLOPT_SSL_VERIFYPEER, FALSE);
            curl_setopt($_curl, CURLOPT_SSL_VERIFYHOST, FALSE);
        }
        curl_setopt($_curl, CURLOPT_URL, $url);
        curl_setopt($_curl, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($_curl, CURLOPT_USERAGENT, 'API PHP CURL');
        curl_setopt($_curl, CURLOPT_HTTPHEADER, $_header);

        if ($expire > 0) {
            curl_setopt($_curl, CURLOPT_TIMEOUT, $expire); // 处理超时时间
            curl_setopt($_curl, CURLOPT_CONNECTTIMEOUT, $expire); // 建立连接超时时间
        }

        // 额外的配置
        if (!empty($extend)) {
            curl_setopt_array($_curl, $extend);
        }

        $result['result'] = curl_exec($_curl);
        $result['code'] = curl_getinfo($_curl, CURLINFO_HTTP_CODE);
        $result['info'] = curl_getinfo($_curl);
        if ($result['result'] === false) {
            $result['result'] = curl_error($_curl);
            $result['code'] = -curl_errno($_curl);
        }

        curl_close($_curl);
        return $result;
    }
}